﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using ApplicationGenerator.BusinessModule.MetaElements;
using ApplicationGenerator.CommonModule;
using ApplicationGenerator.DataAccess;
using ApplicationGenerator.Forms.WebControls;
using VisualEditorUILib;
using WeifenLuo.WinFormsUI.Docking;
using ApplicationGenerator.BusinessModule.Interfaces;

namespace GUserInterface
{
    public delegate void RefreshHandler(string oldName);
    public delegate void UpdatePropertyGridHandler(object toUpdate);
    public delegate void FormSaved(string title);
    public delegate void FormUpdated(string title);
    public delegate void ValidationFailedHandler(List<ErrorEntity> errorList);

    [EditorBrowsable(EditorBrowsableState.Never)]
    [Browsable(false)]
    [DefaultProperty("Title")]
    public partial class FormVEPanel : DockContent, ICustomTypeDescriptor
    {
        #region Events

        public event RefreshHandler RefreshEvent;
        public event UpdatePropertyGridHandler UpdatePropertyGridEvent;
        public event FormSaved FormSavedEvent;
        public event ValidationFailedHandler ValidationFailedEvent;
        //public event FormUpdated FormUpdatedEvent;

        #endregion

        #region Variables

        FormControlContainer fcc;
        FormEditorPanel panelEdt;

        #endregion

        #region Contruction

        public FormVEPanel(int r, int c)
        {
            InitializeComponent();
            fcc = new FormControlContainer(r, c);
            InitializeComponentCustom();
        }

        public FormVEPanel(FormControlContainer _fcc)
        {
            InitializeComponent();
            fcc = _fcc;
            InitializeComponentCustom();
        }

        public FormVEPanel(int r, int c, IMetaModel adpt)
        {
            InitializeComponent();
            fcc = new FormControlContainer(r, c);
            fcc.Source = adpt;
            InitializeComponentCustom();
        }

        private void InitializeComponentCustom()
        {
            panelEdt = new FormEditorPanel(fcc);
            panel1.Controls.Add(panelEdt);
        }

        #endregion

        #region Properties

        public FormEditorPanel FEPanel
        {
            get { return panelEdt; }
            set { panelEdt = value; }
        }

        [Category("Dane podstawowe")]
        [DisplayName("Tytul Formy")]
        [Description("Tytul Formy w Designerze")]
        public String Title
        {
            get { return this.TabText; }
            set
            {
                string oldText = this.TabText;
                this.TabText = value;
                RefreshEvent(oldText);
            }
        }

        #endregion

        #region Methods

        private void button2_Click(object sender, EventArgs e)
        {
            this.Close();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            //Make serialization and save form to database

            List<ErrorEntity> errorList = new List<ErrorEntity>();

            for (int row = 0; row < fcc.RowsCount; row++)
            {
                for (int col = 0; col < fcc.ColumnsCount; col++)
                {
                    BaseControl bc = fcc.GetControl(row, col);
                    if (null != bc)
                    {
                        if (bc is IValidation)
                        {
                            ErrorEntity errEnt = new ErrorEntity();
                            errEnt.Row = row;
                            errEnt.Col = col;
                            if (false == ((IValidation)bc).IsValid(errEnt))
                            {
                                errorList.Add(errEnt);
                                ValidationFailedEvent(errorList);
                                return;
                            }
                        }
                    }
                }
            }

            Guid g = Guid.NewGuid();
            //try to save or update
            //if (false == BusinessModule.Utilities.FormSerializer.SaveFormControlContainter(fcc, g, this.Title))
            if (false == Serializer.Serialize(Policy.Form, fcc, g, this.Title))
            {
                Serializer.Update(Policy.Form, fcc, this.Title);
            }
            else
            {
                FormSavedEvent(this.TabText);
            }

            this.Close();
        }

        private void button3_Click(object sender, EventArgs e)
        {
            UpdatePropertyGridEvent(this);
        }

        #endregion

        private void button4_Click(object sender, EventArgs e)
        {
            panelEdt.RemoveSelectedField();
        }

        #region ICustomTypeDescriptor Members

        public AttributeCollection GetAttributes()
        {
            return TypeDescriptor.GetAttributes(this, true);
        }

        public string GetClassName()
        {
            return TypeDescriptor.GetClassName(this, true);
        }

        public string GetComponentName()
        {
            return TypeDescriptor.GetComponentName(this, true);
        }

        public TypeConverter GetConverter()
        {
            return TypeDescriptor.GetConverter(this, true);
        }

        public EventDescriptor GetDefaultEvent()
        {
            return TypeDescriptor.GetDefaultEvent(this, true);
        }

        public PropertyDescriptor GetDefaultProperty()
        {
            return TypeDescriptor.GetDefaultProperty(this, true);
        }

        public object GetEditor(Type editorBaseType)
        {
            return TypeDescriptor.GetEditor(this, editorBaseType, true);
        }

        public EventDescriptorCollection GetEvents()
        {
            return TypeDescriptor.GetEvents(this, true);
        }

        public EventDescriptorCollection GetEvents(Attribute[] attributes)
        {
            return TypeDescriptor.GetEvents(this, attributes, true);
        }

        public PropertyDescriptorCollection GetProperties(Attribute[] attributes)
        {
            PropertyDescriptorCollection colAvailableCollection = TypeDescriptor.GetProperties(this, attributes, true);
            List<PropertyDescriptor> colDisplayProperties = new List<PropertyDescriptor>();
            colDisplayProperties.Add(colAvailableCollection["Title"]);
            return new PropertyDescriptorCollection(colDisplayProperties.ToArray());
        }

        public PropertyDescriptorCollection GetProperties()
        {
            return TypeDescriptor.GetProperties(this, true);
        }

        public object GetPropertyOwner(PropertyDescriptor pd)
        {
            return this;
        }

        #endregion
    }
}
